﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Runtime.Serialization;
using System.Runtime.Serialization.Formatters.Binary;
using System.Text;
using System.Threading.Tasks;
using System.Xml.Serialization;
using Newtonsoft.Json;

namespace _11_C_中实现深拷贝的五种方式
{
    //[Serializable]
    public class Teacher
    {
        public int TeacherID { get; set; }

        public string TeacherName { get; set; }

        public Student StudentModel { get; set; }

        public Teacher Clone()
        {
            // 使用 MemberwiseClone() 创建浅拷贝 //引用类型复制的引用
            return (Teacher)this.MemberwiseClone();
        }

        //public Teacher DeepClone()//手动深度拷贝
        //{
        //    Teacher tempTeacher = (Teacher)this.MemberwiseClone();

        //    tempTeacher.StudentModel = new Student()
        //    {
        //        StudentID = this.StudentModel.StudentID,
        //        StudentName = this.StudentModel.StudentName
        //    };

        //    return tempTeacher;
        //}

        //public Teacher DeepClone()//二进制序列号拷贝
        //{
        //    //byte[] imageBytes = File.ReadAllBytes("C:\\Users\\nengjupc.mei\\Desktop\\1.jpg"); // 读取一个已有的图像文件作为示例

        //    //序列化的对象类必须带有[Serializable] 特性，否则 BinaryFormatter 无法处理该类。
        //    using (MemoryStream ms = new MemoryStream())
        //    {
        //        //二进制序列化
        //        BinaryFormatter formatter=new BinaryFormatter();

        //        formatter.Serialize(ms,this);

        //        ms.Seek(0,SeekOrigin.Begin);

        //        return (Teacher)formatter.Deserialize(ms);
        //    }

        //}

        //public Teacher? DeepClone()//Json序列化深度拷贝
        //{
        //    string json = JsonConvert.SerializeObject(this);

        //    return JsonConvert.DeserializeObject<Teacher>(json);
        //}

        //public Teacher DeepClone()//xml
        //{

        //    using (MemoryStream ms = new MemoryStream())
        //    {
        //        XmlSerializer xmlSerializer = new XmlSerializer(typeof(Teacher));

        //        xmlSerializer.Serialize(ms,this);

        //        ms.Seek(0,SeekOrigin.Begin);

        //       return (Teacher)xmlSerializer.Deserialize(ms);
        //    }
        //}

        //public Teacher DeepClone()
        //{

        //    using (MemoryStream ms = new MemoryStream())
        //    {
        //        DataContractSerializer dataContract = new DataContractSerializer(typeof(Teacher));

        //        dataContract.WriteObject(ms, this);

        //        ms.Seek(0, SeekOrigin.Begin);

        //        return (Teacher)dataContract.ReadObject(ms);
        //    }
        //} 


        public Teacher DeepClone() //反射
        {
            var teacher = Activator.CreateInstance(typeof(Teacher));
            PropertyInfo[] propertyInfos = teacher.GetType().GetProperties();
            foreach (PropertyInfo propertyInfo in propertyInfos)
            {
                //基础类型和string类型
                if (propertyInfo.PropertyType.IsPrimitive || propertyInfo.PropertyType.Equals(typeof(string)))
                {
                    propertyInfo.SetValue(teacher, propertyInfo.GetValue(this));
                }
                else
                {
                    //实例化里面的引用类型
                    var student = Activator.CreateInstance(propertyInfo.PropertyType);
                    //所有属性
                    PropertyInfo[] stuInfos = propertyInfo.PropertyType.GetProperties();
                    foreach (PropertyInfo stuInfo in stuInfos)
                    {
                        stuInfo.SetValue(student, stuInfo.GetValue(propertyInfo.GetValue(this)));
                    }
                    //属性给teacher对象
                    propertyInfo.SetValue(teacher, student);
                }
            }
            return (Teacher)teacher;
        }
    }
}
